package tpv;

import java.io.BufferedReader;
import java.io.File;
import java.io.FileOutputStream;
import java.io.FileReader;
import java.io.IOException;
import java.io.InputStream;
import java.net.URL;
import java.net.URLConnection;
import java.util.ArrayList;

/**
 * Catálogo con los productos del tpv.
 * @author paco
 */
public class Catalogo
{
    
    public static void main(String[] s)
    {
        Catalogo c = new Catalogo("http://www.dlsi.ua.es/~ccachero/catalogo.csv");
        c.setNumItemes(100);
        c.crearCatalogo();
    }
    /**
     * Numero de items a leer
     */
    private Integer numItemes;
    /**
     * Url con la dirección donde se va a leer el catálogo.
     */
    private String urlCatalogo;
    /**
     * Lista con los productos que componen un catálogo.
     */
    private ArrayList<Producto> productos;

    /**
     * Constructor
     * @param url Direccion del catalogo
     */
    public Catalogo(String url)
    {
        numItemes = 0;
        urlCatalogo = url;
        productos = new ArrayList<Producto>();
    }

    /**
     * Crea el catalogo
     */
    public void crearCatalogo()
    {
        copiarCatalogo();
        File f = new File("catalogo.csv");
        BufferedReader entrada;
        int leidos = 0;
        
        try
        {
            entrada = new BufferedReader(new FileReader(f));
            String producto;
            if (entrada.ready())
            {
                producto = entrada.readLine();
            }
            while (entrada.ready() && leidos < numItemes)
            {
                producto = entrada.readLine();
                leidos++;
                this.procesarLinea(producto);
            }
        }
        catch (IOException e)
        {
            e.printStackTrace();
        }
    }

    /**
     * Lee el catálogo de internet
     */
    public void copiarCatalogo()
    {
        try
        {
            URL url = new URL(this.urlCatalogo);

            // establecemos conexion
            URLConnection urlCon = url.openConnection();

            // Se obtiene el inputStream de la foto web y se abre el fichero
            // local.
            InputStream is = urlCon.getInputStream();

            // Fichero en el que queremos guardar el contenido
            FileOutputStream fos = new FileOutputStream("catalogo.csv");

            // buffer para ir leyendo.
            byte[] array = new byte[1000];

            // Primera lectura y bucle hasta el final
            int leido = is.read(array);
            while (leido > 0)
            {
                fos.write(array, 0, leido);
                leido = is.read(array);
            }

            // Cierre de conexion y fichero.
            is.close();
            fos.close();
            
        }
        catch (Exception e)
        {
            e.printStackTrace();
        }
    }

    /**
     * Añade un nuevo producto al catalago
     * @param linea Producto a añadir
     */
    public void procesarLinea(String linea)
    {
        String[] producto;
        double precio;
        
        producto = linea.split(";");
        producto[0] = parsear(producto[0]);
        
        if (productos == null)
        {
            productos = new ArrayList<Producto>();
        }
        try
        {
            precio = Double.parseDouble(producto[2]);
            Producto p = new Producto(producto[0], producto[1], precio);
            productos.add(p);
        }
        catch (NumberFormatException nfe)
        {
            System.err.println("Formato incorrecto");
        }
    }
    
    /**
     * Devuelve un prodcuto a partir de un código
     * @param codigo Codigo que se quiere encontrar
     * @return Producto que se corresponde con el código o null si no lo encuentra.
     */
    public Producto obtenerItem(String codigo)
    {
        for (Producto p : productos)
        {
            if (p.getCodigo().equals(codigo))
            {
                return p;
            }
        }
        
        return buscarFichero( codigo );

    }
    
    public Producto buscarFichero( String codigo )
    {
        Producto p = null;

        File f = new File("catalogo.csv");
        BufferedReader entrada;
        int leidos = 0;
        
        try
        {
            entrada = new BufferedReader(new FileReader(f));
            String producto;
            if (entrada.ready())
            {
                producto = entrada.readLine();
            }

            while ( entrada.ready() )
            {
                producto = entrada.readLine();
                leidos++;
                if ( this.buscarObjeto( producto, codigo) )
                {
                    try
                    {
                        String [] datos ;
                        datos = producto.split(";");
                        double precio = Double.parseDouble(datos[2]);
                        p = new Producto(datos[0], datos[1], precio);
                        productos.add(p);
                        return p;
                    }
                    catch (NumberFormatException nfe)
                    {
                        System.err.println("Formato incorrecto");
                    }
                }
            }
        }
        catch (IOException e)
        {
            e.printStackTrace();
        }
        
        return p;
    }
    
    public boolean buscarObjeto( String producto, String codigo )
    {        
        String [] datos ;
        datos = producto.split(";");
        return this.parsear(datos[0]).equals(codigo);   
    }
    
    /**
     * Parsea un código dado, eliminando los caracteres que no interesan.
     * @param s Código a parsear.
     * @return Cadena parseada.
     */
    public String parsear( String s )
    {
        String salida = "";
        int indice = s.indexOf(' ') + 1;
        
        salida = s.substring(indice, s.length() - 1);
        
        return salida;
    }
    
    /**
     * Setea el número de items que se quiere buscar
     * @param numItemes Numero de item que se van a incluir en el catálogo.
     */
    public void setNumItemes(Integer numItemes)
    {
        this.numItemes = numItemes;
    }
}
